package com.briup.jd2407cms.service.impl;

import cn.hutool.core.util.ObjUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.briup.jd2407cms.domain.Article;
import com.briup.jd2407cms.domain.Category;
import com.briup.jd2407cms.domain.DTO.ArticleParam;
import com.briup.jd2407cms.domain.User;
import com.briup.jd2407cms.domain.extend.ArticleExtend;
import com.briup.jd2407cms.exception.ServiceException;
import com.briup.jd2407cms.mapper.CategoryMapper;
import com.briup.jd2407cms.mapper.UserMapper;
import com.briup.jd2407cms.service.ArticleService;
import com.briup.jd2407cms.mapper.ArticleMapper;
import com.briup.jd2407cms.util.JwtUtil;
import com.briup.jd2407cms.util.result.ResultCode;
import io.jsonwebtoken.Claims;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.servlet.http.HttpServletRequest;
import java.io.Serializable;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

/**
* @author jay
* @description 针对表【cms_article】的数据库操作Service实现
* @createDate 2024-11-18 14:40:14
*/
@Service
public class ArticleServiceImpl extends ServiceImpl<ArticleMapper, Article>
    implements ArticleService{
    @Autowired
    private UserMapper userMapper;
    @Autowired
    private CategoryMapper categoryMapper;
    @Autowired
    private ArticleMapper articleMapper;

    @Override
    @Transactional(rollbackFor = Throwable.class)
    public boolean saveOrUpdate(Article article, HttpServletRequest request) {
        // 文章状态判断：如果文章已经发表，普通用户不能再修改其标题、内容等信息
        Claims claims = JwtUtil.parseJWT(request.getHeader("Authorization"));
        System.out.println(claims);
        // 1.参数判断
        if(article == null){
            log.error("要操作的文章为空");
            throw new ServiceException(ResultCode.PARAM_IS_BLANK);
        }
        // 2.用户判断：如果用户不存在，则抛异常
        String userId = (String) claims.get("userId");
        if (userId != null && userMapper.selectById(userId) == null){
            log.error("操作文章的用户不存在");
            throw new ServiceException(ResultCode.USER_NOT_EXIST);
        }
        //  3.栏目判断：如果栏目不存在，或栏目不是2级栏目，则抛异常
        Integer categoryId = article.getCategoryId();
        if (categoryId != null){
            Category category = categoryMapper.selectById(categoryId);
            if (category == null || category.getParentId() == null){
                log.error("要放入的栏目无效或不能为一级栏目");
                throw new ServiceException(ResultCode.CATEGORY_NOT_EXIST);
            }
        }

        //saveOrUpdate
        String id = article.getId();
        if (id == null){
            // 4.新增操作
            // 准备文章发表时间
            article.setPublishTime(LocalDateTime.now());
            article.setUserId(userId);

            // 新增文章
            return super.save(article);
        } else {
            // 5.修改操作
            // 判断文章id是否存在
            Article oldArticle = articleMapper.selectById(id);
            if(oldArticle == null){
                log.error("要修改的文章不存在");
                throw new ServiceException(ResultCode.ARTICLE_NOT_EXIST);
            }
            // 普通用户没有权限修改文章
            Integer roleId = (Integer) claims.get("roleId");
            if(roleId == 3 && !article.getStatus().equals(oldArticle.getStatus())){
                log.error("普通用户没有权限修改文章的状态");
                throw new ServiceException(ResultCode.PARAM_IS_INVALID);
            }
            return super.updateById(article);
        }

    }

    @Override
    @Transactional(rollbackFor = Throwable.class)
    public IPage<ArticleExtend> page(ArticleParam articleParam) {
        // 先查询Article
        IPage<Article> page = new Page<>(articleParam.getPageNum(), articleParam.getPageSize());
        LambdaQueryWrapper<Article> lqw = new LambdaQueryWrapper<>();
        lqw.like(!StrUtil.isEmpty(articleParam.getTitle()),Article::getTitle,articleParam.getTitle())
                .eq(!StrUtil.isEmpty(articleParam.getCategoryId()),Article::getCategoryId, articleParam.getCategoryId())
                .eq(!StrUtil.isEmpty(articleParam.getStatus()),Article::getStatus, articleParam.getStatus())
                .eq(!StrUtil.isEmpty(articleParam.getUserId()),Article::getUserId, articleParam.getUserId())
                .eq(articleParam.getCharged() != null,Article::getCharged, articleParam.getCharged())
                .ge(articleParam.getStartTime() != null,Article::getPublishTime, articleParam.getStartTime())
                .le(articleParam.getEndTime() != null,Article::getPublishTime, articleParam.getEndTime())
//                .between(articleParam.getStartTime() != null && articleParam.getEndTime() != null,Article::getPublishTime,
//                        articleParam.getStartTime(), articleParam.getEndTime())
                        ;
        IPage<Article> articleIPage = articleMapper.selectPage(page, lqw);

        // 再拼接成ArticleExtend
        List<Article> records = page.getRecords();
        ArrayList<ArticleExtend> list = new ArrayList<>();
        //遍历所有文章，添加作者信息
        for (Article art : records) {
            // 拷贝Article到ArticleExtend
            ArticleExtend articleExtend = new ArticleExtend();
            BeanUtils.copyProperties(art,articleExtend);
            // 拼接User
            String userId = art.getUserId();
            User user = userMapper.selectById(userId);
            //如果用户已经被删除，则文章不可见
            if(user == null)
                continue;
            //额外注释密码，不能返回给前端
            user.setPassword(null);
            articleExtend.setUser(user);
            list.add(articleExtend);
        }

        return new Page<ArticleExtend>().setRecords(list)
                .setTotal(page.getTotal())
                .setCurrent(page.getCurrent());
    }

    @Override
    @Transactional(rollbackFor = Throwable.class)
    public boolean reviewArticle(String id, String status) {
        // 1.参数判断
        if (StrUtil.isEmpty(id) || StrUtil.isEmpty(status)){
            log.error("审核文章时，传入的id或status为空");
            throw new ServiceException(ResultCode.PARAM_IS_BLANK);
        }

        // 2.文章必须存在
        if (ObjUtil.isEmpty(articleMapper.selectById(id))){
            log.error("要审核的文章不存在");
            throw new ServiceException(ResultCode.ARTICLE_NOT_EXIST);
        }

        // 3.修改文章审核状态
        Article article = new Article();
        article.setId(id);
        article.setStatus(status);

        return articleMapper.updateById(article) == 1;
    }

    @Override
    @Transactional(rollbackFor = Throwable.class)
    public boolean removeByIds(Collection<? extends Serializable> ids) {
        // 1.参数判断
        if (ObjUtil.isEmpty(ids)){
            log.error("传入的要删除资讯id为空");
            throw new ServiceException(ResultCode.PARAM_IS_BLANK);
        }

        // 2.执行批量删除，只要成功删除1条，就算成功，一条都没有删除掉，算失败

        return super.removeByIds(ids);
    }
}




